#!/bin/bash

# Script to extract debug information from log files and compare C and Fortran implementations
# Usage: ./extract_debug_info.sh <log_file>
#        or pipe input to the script: command | ./extract_debug_info.sh

# Create temporary files for input, C and Fortran debug info
INPUT_FILE=$(mktemp)
C_DEBUG_FILE=$(mktemp)
F_DEBUG_FILE=$(mktemp)

# Check if the script is receiving piped input or using a file argument
if [ -t 0 ]; then
  # No pipe, expecting file argument
  if [ $# -lt 1 ]; then
    echo "Usage: $0 <log_file>"
    echo "       or pipe input to the script: command | $0"
    exit 1
  fi

  LOG_FILE="$1"

  # Check if the log file exists
  if [ ! -f "$LOG_FILE" ]; then
    echo "Error: Log file '$LOG_FILE' not found."
    exit 1
  fi
  
  # Copy log file to input file
  cat "$LOG_FILE" > "$INPUT_FILE"
  echo "Extracting debug info from $LOG_FILE..."
else
  # Receiving piped input
  cat > "$INPUT_FILE"
  echo "Extracting debug info from piped input..."
fi

# Initialize arrays to store values
declare -A c_values
declare -A f_values

# Flag to track which section we're in (gcr_rand-f90 or linear-solver-gpu)
in_gcr_section=false

while IFS= read -r line; do
    # Detect which section we're in
    if [[ $line == *"Running gcr_rand-f90"* ]]; then
        in_gcr_section=true
    elif [[ $line == *"Running main project (linear-solver-gpu)"* ]]; then
        in_gcr_section=false
    fi

    # Extract [Fdebug] lines with step numbers
    if [[ $line =~ \[Fdebug\]\ ([^\ ]+)\ step=([0-9]+)\ norm=\ *([0-9.]+) ]]; then
        label="${BASH_REMATCH[1]}"
        step="${BASH_REMATCH[2]}"
        value="${BASH_REMATCH[3]}"
        field="${label}_step_${step}"
        
        if $in_gcr_section; then
            c_values["$field"]=$value
        else
            f_values["$field"]=$value
        fi
    
    # Extract [Cdebug] lines with step numbers
    elif [[ $line =~ \[Cdebug\]\ ([^\ ]+)\ step=([0-9]+)\ norm=([0-9.]+) ]]; then
        label="${BASH_REMATCH[1]}"
        step="${BASH_REMATCH[2]}"
        value="${BASH_REMATCH[3]}"
        field="${label}_step_${step}"
        
        if $in_gcr_section; then
            c_values["$field"]=$value
        else
            f_values["$field"]=$value
        fi

    # Extract [Cdebug] lines without step numbers
    elif [[ $line =~ \[Cdebug\]\ ([^\ ]+)\ norm=\ *([0-9.]+) ]]; then
        label="${BASH_REMATCH[1]}"
        value="${BASH_REMATCH[2]}"
        field="${label}"
        
        if $in_gcr_section; then
            c_values["$field"]=$value
        else
            f_values["$field"]=$value
        fi
    fi
done < "$INPUT_FILE"

# Print the comparison table
echo "+----------------------------------------+--------------------+--------------------+--------------------+"
echo "| Field (Step)                           | Fdebug       | Cdebug  | Difference (%)     |"
echo "+----------------------------------------+--------------------+--------------------+--------------------+"

# Combine all unique field names from both implementations
all_fields=($(echo "${!c_values[@]} ${!f_values[@]}" | tr ' ' '\n' | sort -u))

for field in "${all_fields[@]}"; do
    gcr_val=${c_values[$field]:-"N/A"}
    solver_val=${f_values[$field]:-"N/A"}
    
    # Calculate difference if both values exist
    if [[ $gcr_val != "N/A" && $solver_val != "N/A" ]]; then
        diff=$(echo "scale=2; (($solver_val - $gcr_val)/$gcr_val)*100" | bc)
        diff="${diff}%"
    else
        diff="-"
    fi
    
    printf "| %-38s | %-18s | %-18s | %-18s |\n" "$field" "$gcr_val" "$solver_val" "$diff"
done

echo "+----------------------------------------+--------------------+--------------------+--------------------+"
echo "Debug comparison complete."

# Clean up temp files
rm -f "$INPUT_FILE" "$C_DEBUG_FILE" "$F_DEBUG_FILE" 